<template>
  <div class="p-6px">
    <el-card class="rounded-md" shadow="never">
      <!-- 搜索条件 -->
      <el-form v-show="showSearch" :inline="true" id="searchFormId" @submit.prevent>
        <el-form-item label="分类名称" prop="menuName">
          <el-input placeholder="请输入分类名称" v-model="searchParams.name" clearable style="width: 240px"></el-input>
        </el-form-item>
        <el-form-item>
          <el-button type="primary" icon="search" plain v-throttle="handleSearch">搜索</el-button>
          <el-button type="danger" icon="refresh" plain v-debounce="resetSearch">重置</el-button>
        </el-form-item>
      </el-form>

      <!-- 表格头部按钮 -->
      <el-row :gutter="10">
        <el-col :span="1.5" v-auth="['system:role:add']">
          <el-button type="primary" icon="plus" plain @click="handleAdd()">新增</el-button>
        </el-col>
        <KoiToolbar v-model:showSearch="showSearch" @refresh-table="handleTableData"></KoiToolbar>
      </el-row>

      <br />
      <!-- 数据表格 -->
      <el-table v-if="refreshTreeTable" v-loading="loading" border :data="tableList" v-adaptiveTree
        :default-expand-all="true" :expand-row-keys="expandKey" row-key="id"
        :tree-props="{ children: 'children', hasChildren: 'hasChildren' }" empty-text="暂时没有数据哟">
        <el-table-column label="序号" prop="id" width="80px" align="center" type="index"></el-table-column>
        <el-table-column label="分类名称" prop="name" align="left" :show-overflow-tooltip="true"></el-table-column>
        <el-table-column label="图标" prop="icon" align="center">
          <template #default="scope">
            <el-image :src="scope.row.icon" class="rounded-full w-36px h-36px" :preview-teleported="true"
              :preview-src-list="[scope.row.icon]"></el-image>
          </template>
        </el-table-column>
        <el-table-column label="大图" prop="big_pic" align="center">
          <template #default="scope">
            <el-image :src="scope.row.big_pic" class="rounded-full w-36px h-36px" :preview-teleported="true"
              :preview-src-list="[scope.row.big_pic]"></el-image>
          </template>
        </el-table-column>
        <!-- 注意：如果后端数据返回的是字符串"0" OR "1",这里的active-value AND inactive-value不需要加冒号，会认为是字符串，否则：后端返回是0 AND 1数字，则需要添加冒号 -->
        <el-table-column label="分类状态" prop="status" align="center">
          <template #default="scope">
            <el-switch v-model="scope.row.status" active-text="显示" inactive-text="不显示" :active-value="1"
              :inactive-value="0" :inline-prompt="true" @click="handleSwitch(scope.row)">
            </el-switch>
          </template>
        </el-table-column>
        <el-table-column label="添加时间" prop="create_time" align="left" :show-overflow-tooltip="true"></el-table-column>
        <el-table-column label="排序" prop="sort" align="left" :show-overflow-tooltip="true"></el-table-column>
        <el-table-column label="操作" align="left" width="200" fixed="right">
          <template #default="{ row }">
            <el-button type="primary" size="small" plain @click="handleUpdate(row)" v-auth="['system:role:update']">
              修改
            </el-button>
            <el-button type="danger" size="small" plain @click="handleDelete(row)" v-auth="['system:role:delete']">
              删除
            </el-button>
          </template>
        </el-table-column>
      </el-table>
      <!-- 添加 OR 修改 -->
      <KoiDialog ref="koiDialogRef" :title="title" @koi-confirm="handleConfirm" @koi-cancel="handleCancel"
        :loading="confirmLoading" :height="500">
        <template #content>
          <el-form ref="formRef" :rules="rules" :model="form" label-width="auto" status-icon>
            <!-- 分类级联选择框 -->
            <el-form-item label="分类上级" prop="pid">
              <el-cascader placeholder="请选择分类上级" v-model="form.pid" :options="cascaderOptions" :props="{
                expandTrigger: 'hover',
                emitPath: false,
                checkStrictly: true
              }" filterable clearable style="width: 540px">
                <template #default="{ node, data }">
                  <span>{{ data.label }}</span>
                  <span v-if="!node.isLeaf"> ({{ data.children.length }}) </span>
                </template>
              </el-cascader>
            </el-form-item>

            <el-form-item label="分类名" prop="name">
              <el-input v-model="form.name" placeholder="请输入分类名" clearable />
            </el-form-item>
            <el-form-item label="分类副标题" prop="sub_name">
              <el-input v-model="form.sub_name" placeholder="请输入分类副标题" clearable />
            </el-form-item>
            <el-form-item label="分类描述" prop="desc">
              <el-input v-model="form.desc" placeholder="请输入分类描述" clearable />
            </el-form-item>
            <el-form-item label="icon图标" prop="icon">
              <ColeAttachment v-model:file="form.icon" :limit="1" />
            </el-form-item>
            <el-form-item label="大图" prop="big_pic">
              <ColeAttachment v-model:file="form.big_pic" :limit="1" />
            </el-form-item>
            <el-form-item label="排序" prop="sort">
              <el-input v-model="form.sort" placeholder="请输入排序[0-100 值越大越靠前]" clearable />
            </el-form-item>
            <el-form-item label="是否推荐" prop="is_recommend">
              <el-switch v-model="form.is_recommend" active-text="是" inactive-text="否" :active-value="1"
                :inactive-value="0" :inline-prompt="true">
              </el-switch>
            </el-form-item>
            <el-form-item label="是否显示" prop="status">
              <el-switch v-model="form.status" active-text="是" inactive-text="否" :active-value="1" :inactive-value="0"
                :inline-prompt="true">
              </el-switch>
            </el-form-item>
          </el-form>
        </template>
      </KoiDialog>
    </el-card>
  </div>
</template>

<script setup lang="ts" name="menuPage">
import { ref, reactive, onMounted } from "vue";
import { koiNoticeSuccess, koiNoticeError, koiMsgError, koiMsgWarning, koiMsgBox } from "@/utils/koi.ts";
import { handleTree } from "@/utils/index.ts";
import { listPage, read, cascaderList, add, update, remove, changeStatus } from "@/api/pms/cate/index.ts";

// 数据表格加载页面动画
const loading = ref(false);
/** 是否显示搜索表单 */
const showSearch = ref<boolean>(true); // 默认显示搜索条件

// 数据表格数据
const tableList = ref([]);

// 查询参数
const searchParams = ref({
  name: ""
});

// 重置搜索参数
const resetSearchParams = () => {
  searchParams.value = {
    name: ""
  };
};

/** 搜索 */
const handleSearch = () => {
  handleTableData();
};

/** 重置 */
const resetSearch = () => {
  resetSearchParams();
  handleTreeList();
};

/** 树形表格查询 */
const handleTreeList = async () => {
  try {
    loading.value = true;
    tableList.value = []; // 重置表格数据
    const res: any = await listPage(searchParams.value);
    console.log("分类数据表格数据->", res.data);
    handleExpandKey(res.data);
    tableList.value = handleTree(res.data, "id", "pid");
    loading.value = false;
  } catch (error) {
    console.log(error);
    koiNoticeError("数据查询失败，请刷新重试");
  }
};

/** 树形表格[删除、批量删除等刷新使用] */
const handleTableData = async () => {
  try {
    const res: any = await listPage(searchParams.value);
    console.log("分类数据表格数据->", res.data);
    handleExpandKey(res.data);
    tableList.value = handleTree(res.data, "id", "pid");
  } catch (error) {
    console.log(error);
    koiNoticeError("数据查询失败，请刷新重试");
  }
};

// 展开数据
const expandKey = ref();
/** 展开节点 */
const handleExpandKey = (data: any) => {
  /* 展开节点开始 */
  if (data != null && data.length != 0) {
    expandKey.value = [];
    const resultList: string[] = [];
    data.forEach((obj: any) => {
      if (obj.pid == "0" && obj.isSpread == "0") {
        resultList.push(obj.id);
      }
      if (obj.pid != "0" && obj.isSpread == "0") {
        resultList.push(obj.id);
        resultList.push(obj.pid);
      }
    });
    // 过滤数据
    const uniqueArray = [...new Set(resultList)];
    console.log("展开节点", uniqueArray);
    // 数组必须转为String类型的才生效
    expandKey.value = uniqueArray.map(String);
  } else {
    expandKey.value = [];
  }
};

onMounted(() => {
  // 获取数据表格数据
  handleTreeList();
});


// 级联下拉框
let cascaderOptions = ref([]);
/** 分类级联数据 */
const handleCascader = async () => {
  try {
    cascaderOptions.value = [];
    const res: any = await cascaderList();
    if (res.data != null && res.data != undefined && res.data.length > 0) {
      cascaderOptions.value = handleTree(res.data, "value", "pid");
    }
    // @ts-expect-error
    cascaderOptions.value.unshift({
      label: "最顶级分类",
      value: 0,
      pid: -1
    });
  } catch (error) {
    console.log(error);
    koiMsgError("分类级联数据查询失败，请重试");
  }
};

// 重新渲染表格状态
const refreshTreeTable = ref(true);

/** 添加 */
const handleAdd = () => {
  // 重置表单
  resetForm();
  // 标题
  title.value = "分类添加";
  handleCascader();
  koiDialogRef.value.koiOpen();
};

/** 回显数据 */
const handleEcho = async (id: any) => {
  if (id == null || id == "") {
    koiMsgWarning("请选择需要修改的数据");
    return;
  }
  try {
    const res: any = await read(id);
    form.value = res.data;
  } catch (error) {
    console.log(error);
    koiNoticeError("数据获取失败，请刷新重试");
  }
};

/** 修改 */
const handleUpdate = async (row?: any) => {
  // 重置表单
  resetForm();
  // 标题
  title.value = "分类修改";
  const id = row.id;
  if (id == null || id == "") {
    koiMsgError("请选择需要修改的数据");
  }
  handleCascader();
  // 回显数据
  handleEcho(id);
  koiDialogRef.value.koiOpen();
};

/** 添加 AND 修改弹出框 */
const koiDialogRef = ref();
// 标题
const title = ref("分类管理");
// form表单Ref
const formRef = ref();
// form表单
let form = ref({
  id: "",
  pid: "0",
  name: undefined,
  sub_name: undefined,
  desc: undefined,
  icon: [] as any,
  big_pic: [] as any,
  sort: 0,
  is_recommend: 0,
  status: 1
});

/** 清空表单数据 */
const resetForm = () => {
  form.value = {
    id: "",
    pid: "0",
    name: undefined,
    sub_name: undefined,
    desc: undefined,
    icon: [],
    big_pic: [],
    sort: 0,
    is_recommend: 0,
    status: 1
  };
};

/** 表单规则 */
const rules = reactive({
  pid: [{ required: true, message: "请选择上级分类", trigger: "blur" }],
  name: [{ required: true, message: "请选择分类类型", trigger: "blur" }],
  icon: [{ required: true, message: "请选择图标", trigger: "blur" }]
});

// 确定按钮是否显示loading
const confirmLoading = ref(false);
/** 确定  */
const handleConfirm = () => {
  if (!formRef.value) return;
  confirmLoading.value = true;
  (formRef.value as any).validate(async (valid: any) => {
    if (valid) {
      // console.log("表单ID", form.value.id);
      if (form.value.id != null && form.value.id != "") {
        try {
          await update(form.value);
          koiNoticeSuccess("修改成功");
          confirmLoading.value = false;
          koiDialogRef.value.koiQuickClose();
          resetForm();
          handleTreeList();
        } catch (error) {
          console.log(error);
          confirmLoading.value = false;
          koiNoticeError("修改失败，请刷新重试");
        }
      } else {
        try {
          await add(form.value);
          koiNoticeSuccess("添加成功");
          confirmLoading.value = false;
          koiDialogRef.value.koiQuickClose();
          resetForm();
          handleTreeList();
        } catch (error) {
          console.log(error);
          confirmLoading.value = false;
          koiNoticeError("添加失败，请刷新重试");
        }
      }
    } else {
      koiMsgError("验证失败，请检查填写内容");
      confirmLoading.value = false;
    }
  });
};

/** 取消 */
const handleCancel = () => {
  koiDialogRef.value.koiClose();
};

/** 状态switch */
const handleSwitch = (row: any) => {
  let text = row.status === "0" ? "启用" : "停用";
  koiMsgBox("确认要[" + text + "]-[" + row.menuName + "]分类吗？")
    .then(async () => {
      resetForm();
      if (!row.id || !row.status) {
        koiMsgWarning("请选择需要修改的数据");
        return;
      }
      try {
        await changeStatus(row.id, row.status);
        koiNoticeSuccess("修改成功");
      } catch (error) {
        console.log(error);
        koiNoticeError("修改失败，请刷新重试");
      }
    })
    .catch(() => {
      koiMsgError("已取消");
    });
};

/** 删除 */
const handleDelete = (row: any) => {
  const id = row.id;
  if (id == null || id == "") {
    koiMsgWarning("请选中需要删除的数据");
  }
  koiMsgBox("您确认需要删除分类名称[" + row.menuName + "]么？")
    .then(async () => {
      try {
        await remove(id);
        koiNoticeSuccess("删除成功");
        handleTableData();
      } catch (error) {
        console.log(error);
      }
    })
    .catch(() => {
      koiMsgError("已取消");
    });
};
</script>

<style lang="scss" scoped></style>
